/*
 * Noise generation for PuTTY's cryptographic random number
 * generator.
 */

#include "stdafx.h"
#include "tree234.h"
#include "sshlib.h"
#include <network.h>
#include "bufchain.h"

#include "ssh.h"


/*
 * This function is called once, at PuTTY startup, and will do some
 * seriously silly things like listing directories and getting disk
 * free space and a process snapshot.
 * Y.K. There are better variants - get local weather data, snipping timer ticks, get mouse coordinates, 
 * checking CRC of name of the computer, process ID, etc
 */

void noise_get_heavy(void (*func) (void *, int))
{
	POINT pt;

	GetCursorPos(&pt);

	wchar_t name[MAX_PATH];
	DWORD rseed=MAX_PATH;

	GetComputerName(name,&rseed);

	rseed = rseed + (GetCurrentProcessId() << 1);
	rseed = rseed<<1;
	rseed+=pt.x;
	rseed = rseed<<1;
	rseed+=pt.y;
	rseed = rseed<<1;
	wchar_t *p=name;while (*p!=L'\0') {rseed+=*p;p++;}
	rseed = rseed<<12;
	rseed = rseed+(GETTICKCOUNT() & 0xFFFF);
	func(&rseed, sizeof(rseed));
}

/*
 * This function is called every time the random pool needs
 * stirring, and will acquire the system time in all available
 * forms.
 */
void noise_get_light(void (*func) (void *, int))
{
    SYSTEMTIME systime;
    DWORD adjust[2];
    BOOL rubbish;

    GetSystemTime(&systime);
    func(&systime, sizeof(systime));

    GetSystemTimeAdjustment(&adjust[0], &adjust[1], &rubbish);
    func(&adjust, sizeof(adjust));
}

/*
 * This function is called on a timer, and it will monitor
 * frequently changing quantities such as the state of physical and
 * virtual memory, the state of the process's message queue, which
 * window is in the foreground, which owns the clipboard, etc.
 */
void noise_regular(void)
{
    HWND w;
    DWORD z;
    POINT pt;
    MEMORYSTATUS memstat;
    FILETIME times[4];

    w = GetForegroundWindow();
    random_add_noise(&w, sizeof(w));
    w = GetCapture();
    random_add_noise(&w, sizeof(w));
    w = GetClipboardOwner();
    random_add_noise(&w, sizeof(w));
    z = GetQueueStatus(QS_ALLEVENTS);
    random_add_noise(&z, sizeof(z));

    GetCursorPos(&pt);
    random_add_noise(&pt, sizeof(pt));

    GlobalMemoryStatus(&memstat);
    random_add_noise(&memstat, sizeof(memstat));

    GetThreadTimes(GetCurrentThread(), times, times + 1, times + 2,
		   times + 3);
    random_add_noise(&times, sizeof(times));
    GetProcessTimes(GetCurrentProcess(), times, times + 1, times + 2,
		    times + 3);
    random_add_noise(&times, sizeof(times));
}

/*
 * This function is called on every keypress or mouse move, and
 * will add the current Windows time and performance monitor
 * counter to the noise pool. It gets the scan code or mouse
 * position passed in.
 */
void noise_ultralight(unsigned long data)
{
    DWORD wintime;
    LARGE_INTEGER perftime;

    random_add_noise(&data, sizeof(DWORD));

    wintime = GetTickCount();
    random_add_noise(&wintime, sizeof(DWORD));

    if (QueryPerformanceCounter(&perftime))
	random_add_noise(&perftime, sizeof(perftime));
}
